package cn.xlbweb.cli.service.impl;

import cn.xlbweb.cli.mapper.PermissionMapper;
import cn.xlbweb.cli.mapper.RoleMapper;
import cn.xlbweb.cli.mapper.RolePermissionMapper;
import cn.xlbweb.cli.mapper.UserMapper;
import cn.xlbweb.cli.model.*;
import cn.xlbweb.cli.common.ServerResponse;
import cn.xlbweb.cli.common.TableResponse;
import cn.xlbweb.cli.common.TreeResponse;
import cn.xlbweb.cli.pojo.dto.RolesListDTO;
import cn.xlbweb.cli.service.IRoleService;
import cn.xlbweb.cli.util.CliUtils;
import cn.xlbweb.cli.pojo.vo.PermissionVO;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.List;

/**
 * @author: bobi
 * @date: 2019-09-16 23:17
 * @description:
 */
@Service
@Slf4j
public class RoleServiceImpl implements IRoleService {

    @Autowired
    private RoleMapper roleMapper;

    @Autowired
    private UserMapper userMapper;

    @Autowired
    private PermissionMapper permissionMapper;

    @Autowired
    private RolePermissionMapper rolePermissionMapper;

    @Override
    public TableResponse listRoles(RolesListDTO rolesListDTO, int pageNum, int pageSize) {
        log.info("listRoles() start...");
        // 构造查询条件
        RoleExample roleExample = new RoleExample();
        if (StringUtils.isNotBlank(rolesListDTO.getName())) {
            roleExample.createCriteria().andNameLike("%" + rolesListDTO.getName() + "%");
        }
        // 构建分页
        PageHelper.startPage(pageNum, pageSize);
        List<Role> roleList = roleMapper.selectByExample(roleExample);
        PageInfo<Role> rolePageInfo = new PageInfo<>(roleList);
        // 构建Vo
        for (Role role : roleList) {
            // 创建者
            int createByUserId = Integer.parseInt(role.getCreateBy());
            User createByUser = userMapper.selectByPrimaryKey(createByUserId);
            role.setCreateBy(createByUser.getUsername());
            // 更新者
            int updateByUserId = Integer.parseInt(role.getUpdateBy());
            User updateByUser = userMapper.selectByPrimaryKey(updateByUserId);
            role.setUpdateBy(updateByUser.getUsername());
        }
        log.info("listRoles() end...");
        return TableResponse.success(rolePageInfo.getTotal(), roleList);
    }

    @Transactional(rollbackFor = Exception.class)
    @Override
    public ServerResponse insertRole(Role role) {
        // 判断角色名是否已经存在
        if (getRoleByName(role.getName()) != null) {
            return ServerResponse.error("角色名已存在");
        }
        // 插入角色
        int count = roleMapper.insertSelective(role);
        if (count > 0) {
            return ServerResponse.success("添加成功");
        }
        return ServerResponse.error("插入失败");
    }

    @Transactional(rollbackFor = Exception.class)
    @Override
    public ServerResponse updateRole(Role role) {
        // 判断角色名是否已经存在
        Role dbRole = roleMapper.selectByPrimaryKey(role.getId());
        if (!StringUtils.equals(role.getName(), dbRole.getName()) && getRoleByName(role.getName()) != null) {
            return ServerResponse.error("角色名已存在");
        }
        // 更新角色
        int count = roleMapper.updateByPrimaryKeySelective(role);
        if (count > 0) {
            return ServerResponse.success("更新成功");
        }
        return ServerResponse.error("更新失败");
    }

    @Transactional(rollbackFor = Exception.class)
    @Override
    public ServerResponse deleteRole(String ids) {
        // 删除该角色所拥有的所有权限
        deleteRolePermission(ids);
        // 构建删除条件
        RoleExample roleExample = new RoleExample();
        roleExample.createCriteria().andIdIn(CliUtils.getIdList(ids));
        // 删除角色
        int count = roleMapper.deleteByExample(roleExample);
        if (count > 0) {
            return ServerResponse.success("删除成功");
        }
        return ServerResponse.error("删除失败");
    }

    @Override
    public TreeResponse getTree(Integer roleId) {
        // 查询所有权限
        List<Permission> permissionList = permissionMapper.selectByExample(null);
        // 构建Vo
        List<PermissionVO> permissionVOList = CliUtils.getPermissionTree(permissionList, 0);
        // 查询该角色所拥有的全部权限集合
        RolePermissionExample rolePermissionExample = new RolePermissionExample();
        rolePermissionExample.createCriteria().andRoleIdEqualTo(roleId);
        List<RolePermission> rolePermissionList = rolePermissionMapper.selectByExample(rolePermissionExample);
        List<Integer> roleHaveIds = new ArrayList<>();
        for (RolePermission rolePermission : rolePermissionList) {
            roleHaveIds.add(rolePermission.getPermissionId());
        }
        return TreeResponse.success(roleHaveIds, permissionVOList);
    }

    @Override
    public ServerResponse authorize(Integer roleId, String permissionIds) {
        // 删除该角色所拥有的所有权限
        RolePermissionExample rolePermissionExample = new RolePermissionExample();
        rolePermissionExample.createCriteria().andRoleIdEqualTo(roleId);
        rolePermissionMapper.deleteByExample(rolePermissionExample);
        // 赋权
        for (Integer permissionId : CliUtils.getIdList(permissionIds)) {
            RolePermission rolePermission = new RolePermission();
            rolePermission.setRoleId(roleId);
            rolePermission.setPermissionId(permissionId);
            Role role = roleMapper.selectByPrimaryKey(roleId);
            Permission permission = permissionMapper.selectByPrimaryKey(permissionId);
            rolePermission.setRemarks(role.getName() + "-" + permission.getName());
            rolePermissionMapper.insertSelective(rolePermission);
        }
        return ServerResponse.success("赋权成功");
    }

    private Role getRoleByName(String name) {
        RoleExample roleExample = new RoleExample();
        roleExample.createCriteria().andNameEqualTo(name);
        List<Role> roleList = roleMapper.selectByExample(roleExample);
        return roleList.get(0);
    }

    private void deleteRolePermission(String roleIds) {
        List<Integer> idList = CliUtils.getIdList(roleIds);
        RolePermissionExample rolePermissionExample = new RolePermissionExample();
        rolePermissionExample.createCriteria().andRoleIdIn(idList);
        int count = rolePermissionMapper.deleteByExample(rolePermissionExample);
        log.info("成功删除{}条角色的权限信息", count);
    }
}
